#pragma once

#include <osgViewer/CompositeViewer>
#include "VRPNClientManager.h"

class CCaveViewer :	public osgViewer::CompositeViewer
{
public:
	enum CaveFaceId
	{
		CAVE_CENTER = 0,
		CAVE_RIGHT,
		CAVE_LEFT,
		CAVE_BOTTOM
	};

	CCaveViewer();
	virtual ~CCaveViewer();

	void setCaveFaceId(CaveFaceId id);
	void setEyeDistance(double dist);
	void setViewportShift(unsigned int dist);
	void setStartEye(const osg::Vec3& eye);
	void setCaveDimensions(double width, double height, double depth);
	void setGroundDimensions(double top, double bottom);
	void setSceneScale(double x, double y, double z);
	void setLightPos(const osg::Vec3 pos);

	void init();
	void setScene(osg::Node* scene);

	virtual void frame(double simulationTime = USE_REFERENCE_TIME);

private:
	osg::Vec2 m_windowSize;
	unsigned int m_shiftWidth;
	
	double m_caveWidth;
	double m_caveHeight;
	double m_caveDepth;
	double m_caveGroundTop;
	double m_caveGroundBottom;
	osg::Vec3 m_sceneScale;
	osg::Vec3 m_lightPos;

	double m_eyeDist;

	osg::Vec3 m_startEye;
	
	osg::ref_ptr<osg::Camera> m_leftCamera;
	osg::ref_ptr<osg::Camera> m_rightCamera;

	osgViewer::View* m_leftView;
	osgViewer::View* m_rightView;

	CaveFaceId m_caveFaceId;

	osg::ref_ptr<osg::PositionAttitudeTransform> m_sceneRotationPat;
	osg::ref_ptr<osg::PositionAttitudeTransform> m_scenePositionPat;

	CVRPNClientManager m_VRPNClientManager;
};

inline void CCaveViewer::setEyeDistance(double dist)
{
	m_eyeDist = dist;
}

inline void CCaveViewer::setViewportShift(unsigned int dist)
{
	m_shiftWidth = dist;
}

inline void CCaveViewer::setStartEye(const osg::Vec3& eye)
{
	m_startEye = eye;
}

inline void CCaveViewer::setCaveDimensions(double width, double height, double depth)
{
	m_caveWidth = width;
	m_caveHeight = height;
	m_caveDepth = depth;
}

inline void CCaveViewer::setGroundDimensions(double top, double bottom)
{
	m_caveGroundTop = top;
	m_caveGroundBottom = bottom;
}

inline void CCaveViewer::setSceneScale(double x, double y, double z)
{
	m_sceneScale = osg::Vec3(x, y, z);
}

inline void CCaveViewer::setCaveFaceId(CaveFaceId id)
{
	m_caveFaceId = id;
}

inline void CCaveViewer::setLightPos(const osg::Vec3 pos)
{
	m_lightPos = pos;
}